﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections.Specialized;
using System.IO;
using System.Net;
using System.Security.Cryptography.X509Certificates;
using System.Net.Security;

namespace TC.SSO.Client.Common
{
    internal sealed class HttpUtility
    {
        private static readonly string _defalutUserAgent = "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.1; Trident/6.0)";
        public static HttpWebResponse CreateHttpGetResponse(string uri)
        {
            return CreateHttpGetResponse(uri, null);
        }
        public static HttpWebResponse CreateHttpGetResponse(string uri, CookieCollection cookies)
        {
            return CreateHttpGetResponse(uri, cookies, null, null);
        }
        /// <summary>
        /// 发送HTTPGET请求
        /// </summary>
        /// <param name="uri">请求页面地址</param>
        /// <param name="cookies">Cookie集合</param>
        /// <param name="timeout">超时时间（分钟）</param>
        /// <param name="userAgent"></param>
        /// <returns></returns>
        public static HttpWebResponse CreateHttpGetResponse(string uri, CookieCollection cookies, int? timeout, string userAgent)
        {
            if (string.IsNullOrEmpty(uri))
            {
                throw new ArgumentNullException("uri");
            }
            HttpWebRequest request = WebRequest.Create(uri) as HttpWebRequest;
            request.Timeout = (timeout ?? 1) * 60 * 1000;
            request.UserAgent = string.IsNullOrEmpty(userAgent) ? _defalutUserAgent : userAgent;
            request.Method = "GET";
            request.AllowAutoRedirect = false;//禁止自动重定向
            if (cookies != null)
            {
                request.CookieContainer = new CookieContainer();
                request.CookieContainer.Add(cookies);
            }
            return request.GetResponse() as HttpWebResponse;
        }
        public static HttpWebResponse CreateHttpPostResponse(string uri, IDictionary<string, string> paramters)
        {
            return CreateHttpPostResponse(uri, paramters, null);
        }
        public static HttpWebResponse CreateHttpPostResponse(string uri, IDictionary<string, string> paramters, CookieCollection cookies)
        {
            return CreateHttpPostResponse(uri, paramters, cookies, null);
        }
        public static HttpWebResponse CreateHttpPostResponse(string uri, IDictionary<string, string> paramters, CookieCollection cookies, string referer)
        {
            return CreateHttpPostResponse(uri, paramters, cookies, referer, System.Text.Encoding.UTF8, null, null);
        }
        /// <summary>
        /// 发送HTTPPOST请求
        /// </summary>
        /// <param name="uri">请求的url</param>
        /// <param name="paramters">请求参数</param>
        /// <param name="cookies">Cookie集合</param>
        /// <param name="referer">RefferHTTP标头</param>
        /// <param name="encoding">编码方式</param>
        /// <param name="timeout">超时时间</param>
        /// <param name="userAgent"></param>
        /// <returns></returns>
        public static HttpWebResponse CreateHttpPostResponse(string uri, IDictionary<string, string> paramters, CookieCollection cookies, string referer, System.Text.Encoding encoding, int? timeout, string userAgent)
        {
            if (paramters != null && paramters.Count != 0)
            {
                System.Text.StringBuilder sb = new System.Text.StringBuilder();
                int index = 0;
                foreach (var dic in paramters)
                {
                    if (index == 0)
                    {
                        sb.AppendFormat("{0}={1}", dic.Key, System.Web.HttpUtility.UrlEncode(dic.Value));
                    }
                    else
                    {
                        sb.AppendFormat("&{0}={1}", dic.Key, System.Web.HttpUtility.UrlEncode(dic.Value));
                    }
                    index++;
                }
                return CreateHttpPostResponse(uri, sb.ToString(), cookies, referer, encoding, timeout, userAgent);
            }
            return CreateHttpPostResponse(uri, "", cookies, referer, encoding, timeout, userAgent);
        }
        public static HttpWebResponse CreateHttpPostResponse(string uri, string postString)
        {
            return CreateHttpPostResponse(uri, postString, null, null, System.Text.Encoding.UTF8, null, null);
        }
        public static HttpWebResponse CreateHttpPostResponse(string uri, string postString, CookieCollection cookies, string referer, System.Text.Encoding encoding, int? timeout, string userAgent)
        {
            if (string.IsNullOrEmpty(uri))
            {
                throw new ArgumentNullException("uri");
            }
            if (encoding == null)
            {
                throw new ArgumentNullException("encoding");
            }
            HttpWebRequest request;
            //发送的是https请求
            if (uri.StartsWith("https"))
            {
                ServicePointManager.ServerCertificateValidationCallback = new RemoteCertificateValidationCallback(CheckValidationResult);
                request = WebRequest.Create(uri) as HttpWebRequest;
                request.ProtocolVersion = HttpVersion.Version10;
            }
            else
            {
                request = WebRequest.Create(uri) as HttpWebRequest;
            }
            CookieContainer container = new CookieContainer();
            request.Method = "POST";
            request.ContentType = "application/x-www-form-urlencoded; charset=UTF-8";
            request.Timeout = (timeout ?? 1) * 60 * 1000;
            request.UserAgent = string.IsNullOrEmpty(userAgent) ? _defalutUserAgent : userAgent;
            request.AllowAutoRedirect = false;//禁止自动重定向
            request.CookieContainer = container;
            //设置伪装的Referre标头
            if (!string.IsNullOrEmpty(referer))
            {
                request.Referer = referer;
            }
            if (cookies != null)
            {
                request.CookieContainer.Add(cookies);
            }
            if (!string.IsNullOrEmpty(postString))
            {
                byte[] data = encoding.GetBytes(postString);
                request.ContentLength = data.Length;
                using (Stream sm = request.GetRequestStream())
                {
                    sm.Write(data, 0, data.Length);
                }
            }
            return request.GetResponse() as HttpWebResponse;
        }
        private static bool CheckValidationResult(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors errors)
        {
            return true; //总是接受  
        }

        public static HttpWebResponse CreatePostFileResponse(string uri, string file)
        {
            if (string.IsNullOrEmpty(uri))
            {
                throw new ArgumentNullException();
            }
            if (string.IsNullOrEmpty(file))
            {
                throw new ArgumentNullException();
            }
            //边界
            string boundary = DateTime.Now.Ticks.ToString("x");
            var uploadRequest = (HttpWebRequest)WebRequest.Create(uri);//url为上传的地址
            uploadRequest.ContentType = "multipart/form-data; boundary=" + boundary;
            uploadRequest.Method = "POST";
            uploadRequest.Accept = "*/*";
            uploadRequest.KeepAlive = true;
            uploadRequest.Headers.Add("Accept-Language", "zh-cn");
            uploadRequest.Headers.Add("Accept-Encoding", "gzip, deflate");
            uploadRequest.Credentials = System.Net.CredentialCache.DefaultCredentials;
            //uploadRequest.Headers["Cookie"] = cookies;//上传文件时需要的cookies

            WebResponse reponse;
            //创建一个内存流
            Stream memStream = new MemoryStream();
            boundary = "--" + boundary;

            //添加上传文件参数格式边界
            string paramFormat = boundary + "\r\nContent-Disposition: form-data; name=\"{0}\";\r\n\r\n{1}\r\n";
            NameValueCollection param = new NameValueCollection();
            param.Add("fname", Guid.NewGuid().ToString() + Path.GetExtension(file));

            //写上参数
            foreach (string key in param.Keys)
            {
                string formitem = string.Format(paramFormat, key, param[key]);
                byte[] formitembytes = System.Text.Encoding.UTF8.GetBytes(formitem);
                memStream.Write(formitembytes, 0, formitembytes.Length);
            }

            //添加上传文件数据格式边界
            string dataFormat = boundary + "\r\nContent-Disposition: form-data; name=\"{0}\";filename=\"{1}\"\r\nContent-Type:application/octet-stream\r\n\r\n";
            string header = string.Format(dataFormat, "Filedata", Path.GetFileName(file));
            byte[] headerbytes = System.Text.Encoding.UTF8.GetBytes(header);
            memStream.Write(headerbytes, 0, headerbytes.Length);

            //获取文件内容
            FileStream fileStream = new FileStream(file, FileMode.Open, FileAccess.Read);
            byte[] buffer = new byte[1024];
            int bytesRead = 0;

            //将文件内容写进内存流
            while ((bytesRead = fileStream.Read(buffer, 0, buffer.Length)) != 0)
            {
                memStream.Write(buffer, 0, bytesRead);
            }
            fileStream.Close();

            //添加文件结束边界
            byte[] boundarybytes = System.Text.Encoding.UTF8.GetBytes("\r\n\n" + boundary + "\r\nContent-Disposition: form-data; name=\"Upload\"\r\n\nSubmit Query\r\n" + boundary + "--");
            memStream.Write(boundarybytes, 0, boundarybytes.Length);

            //设置请求长度
            uploadRequest.ContentLength = memStream.Length;
            //获取请求写入流
            Stream requestStream = uploadRequest.GetRequestStream();


            //将内存流数据读取位置归零
            memStream.Position = 0;
            byte[] tempBuffer = new byte[memStream.Length];
            memStream.Read(tempBuffer, 0, tempBuffer.Length);
            memStream.Close();

            //将内存流中的buffer写入到请求写入流
            requestStream.Write(tempBuffer, 0, tempBuffer.Length);
            requestStream.Close();
            return uploadRequest.GetResponse() as HttpWebResponse;
        }
    }
}
